/*
 * drv_encoder.c
 *
 *  Created on: 01/04/2014
 *      Author: f98877a
 */

#include "Comum.h"

#include "drivers/drv_encoder.h"


static unsigned char g_ucEncoderStates = ALL_ENCODERS;


unsigned char
EncoderPoll(unsigned char *pucDelta, unsigned char *pucRawState)
{
    unsigned long ulDelta;
    unsigned long ulData;
    static unsigned char ucSwitchClockA = 0;
    static unsigned char ucSwitchClockB = 0;

    //
    // Read the raw state of the push buttons.  Save the raw state
    // (inverting the bit sense) if the caller supplied storage for the
    // raw value.
    //
    ulData = (ROM_GPIOPinRead(ENCODERS_GPIO_BASE, ALL_ENCODERS));
    if(pucRawState)
    {
        *pucRawState = (unsigned char)~ulData;
    }

    //
    // Determine the switches that are at a different state than the debounced
    // state.
    //
    ulDelta = ulData ^ g_ucEncoderStates;

    //
    // Increment the clocks by one.
    //
    ucSwitchClockA ^= ucSwitchClockB;
    ucSwitchClockB = ~ucSwitchClockB;

    //
    // Reset the clocks corresponding to switches that have not changed state.
    //
    ucSwitchClockA &= ulDelta;
    ucSwitchClockB &= ulDelta;

    //
    // Get the new debounced switch state.
    //
    g_ucEncoderStates &= ucSwitchClockA | ucSwitchClockB;
    g_ucEncoderStates |= (~(ucSwitchClockA | ucSwitchClockB)) & ulData;

    //
    // Determine the switches that just changed debounced state.
    //
    ulDelta ^= (ucSwitchClockA | ucSwitchClockB);

    //
    // Store the bit mask for the buttons that have changed for return to
    // caller.
    //
    if(pucDelta)
    {
        *pucDelta = (unsigned char)ulDelta;
    }

    //
    // Return the debounced buttons states to the caller.  Invert the bit
    // sense so that a '1' indicates the button is pressed, which is a
    // sensible way to interpret the return value.
    //
    return(~g_ucEncoderStates);
}


extern BRTOS_Sem *sEncoder;

/*******************************************************************************
 * @NAME:               EncodersHandler                                        *
 * @BRIEF:              Handles the interruption of encoder PORTE  			   *
 * @CREATED_BY:         Ricardo Sa                                              *
 * @CREATION_DATE:      01 abr 2014                                             *
 * @SPEC_REF:                                                                   *
 * @LIB_REF:                                                                    *
 * @LIB_REUSE_%:                                                                *
 *******************************************************************************/
void EncodersHandler(void)
{
	GPIOPinIntClear(ENCODERS_GPIO_BASE, ALL_ENCODERS);
	GPIOPinIntDisable(ENCODERS_GPIO_BASE, ALL_ENCODERS);

	// Call the keyboard analysis task
	OSSemPost(sEncoder);

    // ************************
    // Interrupt Exit
    // ************************
    OS_INT_EXIT_EXT();
    // ************************
}




